package Services;

import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.net.HttpURLConnection;
import java.net.MalformedURLException;
import java.net.ProtocolException;
import java.net.URL;
import java.net.URLEncoder;

public class FBMailman {


	private static String access_token_location = "https://graph.facebook.com/oauth/access_token?" +
			"client_id=" + Entities.FBCommons.getAppID() +
			"&client_secret=" + Entities.FBCommons.getAppSecret() + "&" +
			"grant_type=client_credentials";

	private static String grapURL = "https://graph.facebook.com";


	/* [code copied from the great Alibaba project]
	 * reads byte[] from inputstream
	 * 
	 */

	public static byte[] readInputStream(InputStream stream) throws IOException {
		final int chunkSize = 2048;
		byte[] buf = new byte[chunkSize];
		ByteArrayOutputStream byteStream = new ByteArrayOutputStream(chunkSize);
		int count;
		while ((count=stream.read(buf)) != -1) byteStream.write(buf, 0, count);
		return byteStream.toByteArray();
	}


	/* get the app's access token
	 * 
	 */
	public static String getAccessToken(){
		URL url;
		try {
			url = new URL(access_token_location);
		} catch (MalformedURLException e) {
			System.out.println("getAccessToken: bad url");
			return null;
		}
		HttpURLConnection connection = null;
		try {
			connection = (HttpURLConnection)url.openConnection();
		} catch (IOException e) {
			System.out.println("getAccessToken: IOException");
			return null;

		}
		try {
			connection.setRequestMethod("GET");
			connection.connect();
			int rc = connection.getResponseCode();
			if (rc == HttpURLConnection.HTTP_OK){

				byte[] barr = readInputStream(connection.getInputStream());
				String acess_token = new String(barr);
				return acess_token;
			}
			else {
				System.out.println("an error has occured - couldn't retrieve access token");
				return null;
			}		
		} catch (ProtocolException e) {
			return null;
		} catch (IOException e) {
			return null;
		}


	}


	/* post a comment on a user's facebook wall
	 * @param String fb_uid: a string of the facebook user's ID number.
	 * @param String comment: a comment string to post on the user's wall 
	 * 
	 */
	public static boolean postToWall(String fb_uid, String comment){

		String access_token = getAccessToken();
		if (access_token == null){
			System.out.println("could not get an access_token");
			return false;
		}
		// create the url for the request
		URL url = null;
		try {
			url = new URL(grapURL + "/" + fb_uid +
										"/feed?" +
										access_token
					);
		} 
		catch (MalformedURLException e) {
			System.out.println("MalformedURLException - check the url");
			e.printStackTrace();
			return false;
		}

		// open HTTP conenction by the url
		HttpURLConnection connection = null;
		try {
			connection = (HttpURLConnection)url.openConnection();
		} catch (IOException e) {
			System.out.println("IOException occured");
			e.printStackTrace();
			return false;
		}

		// set connection properties
		try {
			// set the conn. method to post and add the message to conn. body
			connection.setRequestMethod("POST");
			connection.setDoOutput(true);
			OutputStream out = connection.getOutputStream();
			String body = "message=" + comment + 
						  "&link=donutrush.appspot.com" +
						  "&caption=Donut Rush!";
			out.write(body.getBytes());
			out.flush();

			connection.connect();

			// check the response
			int rc = connection.getResponseCode();
			if (rc == HttpURLConnection.HTTP_BAD_REQUEST) {
				System.out.println("postToWall: msg #400: request didn't work");
				return false;
			} 
			else if (rc == HttpURLConnection.HTTP_FORBIDDEN){
				System.out.println("postToWall: msg #403:not allowed to post to this user's wall");
				System.out.println("check the user's permissions include publish_stream");
				return false;
			}

			// parse the response body
			byte[] b = readInputStream(connection.getInputStream());
			String p = new String(b);
			System.out.println(p);


		} 
		catch (ProtocolException e) {
			e.printStackTrace();
			return false;
		}
		catch (IOException e) {
			e.printStackTrace();
			return false;
		}		

		return true;
	}
	
	
	/* post a score to user's timeline
	 * @param String fb_uid: a string of the facebook user's ID number.
	 * @param int score: The score we want to post 
	 * 
	 */
	public static boolean postScoreToTimeLine(String fb_uid, int score){

		String access_token = getAccessToken();
		if (access_token == null){
			System.out.println("could not get an access_token");
			return false;
		}
		// create the url for the request
		URL url = null;
		
		//https://graph.facebook.com/USER_ID/scores?score=USER_SCORE&access_token=APP_ACCESS_TOKEN
		try {
			url = new URL(grapURL + "/" + fb_uid +
										"/scores?" +
										access_token
					);
		} 
		catch (MalformedURLException e) {
			System.out.println("MalformedURLException - check the url");
			e.printStackTrace();
			return false;
		}

		// open HTTP conenction by the url
		HttpURLConnection connection = null;
		try {
			connection = (HttpURLConnection)url.openConnection();
		} catch (IOException e) {
			System.out.println("IOException occured");
			e.printStackTrace();
			return false;
		}

		// set connection properties
		try {
			// set the conn. method to post and add the message to conn. body
			connection.setRequestMethod("POST");
			connection.setDoOutput(true);
			OutputStream out = connection.getOutputStream();
			String body = "score=" + score;
			out.write(body.getBytes());
			out.flush();

			connection.connect();

			// check the response
			int rc = connection.getResponseCode();
			if (rc == HttpURLConnection.HTTP_BAD_REQUEST) {
				System.out.println("postScoreToTimeLine: msg #400: request didn't work");
				return false;
			} 
			else if (rc == HttpURLConnection.HTTP_FORBIDDEN){
				System.out.println("postScoreToTimeLine: msg #403:not allowed to post to this user's wall");
				System.out.println("check the user's permissions include publish_stream");
				return false;
			}

			// parse the response body
			byte[] b = readInputStream(connection.getInputStream());
			String p = new String(b);
			System.out.println(p);


		} 
		catch (ProtocolException e) {
			e.printStackTrace();
			return false;
		}
		catch (IOException e) {
			e.printStackTrace();
			return false;
		}		

		return true;
	}
	

	/* get user's permissions by facebook user ID
	 * 
	 */
	public static boolean getPerms(String fb_uid){

		String access_token = getAccessToken();
		if (access_token == null){
			System.out.println("BAD! ACCESS_TOKEN BAD!");
		}
		URL url = null;
		try {
			String url_string = "https://graph.facebook.com/" + fb_uid + "/permissions?" + access_token;
			url = new URL(url_string);
		} catch (MalformedURLException e) {
			System.out.println("MalformedURLException - check the url");
			e.printStackTrace();
		}

		// open HTTP conenction by the url
		HttpURLConnection connection = null;
		try {
			connection = (HttpURLConnection)url.openConnection();
		} catch (IOException e) {
			System.out.println("IOException occured");
			e.printStackTrace();
		}

		// set connection properties
		try {
			connection.setRequestMethod("GET");
			connection.connect();

			int rc = connection.getResponseCode();
			if (rc == HttpURLConnection.HTTP_BAD_REQUEST) {
				System.out.println("didn't work");
				return false;
			} 

			byte[] b = readInputStream(connection.getInputStream());
			String p = new String(b);
			System.out.println(p);
			int nameIndex = p.indexOf("\"name\":");
			int headIndex = p.indexOf(":", nameIndex);
			int tailIndex = p.indexOf(",", headIndex);
			String name = p.substring(headIndex+2, tailIndex-1);
			System.out.println(name);			
			return true;

		} 
		catch (ProtocolException e) {
			e.printStackTrace();
		}
		catch (IOException e) {
			e.printStackTrace();
		}		

		return false;
	}


	public static void main(String args[]){
		// holed interator's id is: 100000579772008
		// the donut rush community id is: 343383955679333
		//getName("343383955679333");
		//getPerms("343383955679333");
		//getPageAccessToken("100000579772008");
		//postToWall("100003362692872", "TEST2");
		//postScoreToTimeLine("100000579772008",30);
		return;
	}
}
